<?php
namespace api\modules\v1\models\userFund;

use api\modules\v1\models\user\User;
use api\modules\v1\models\userReceipt\ReceiptBank;
use common\models\CacheKeys;
use common\models\Functions;
use common\models\im\Im;
use common\models\Patterns;
use common\models\shop\GoodsOrder;
use common\models\Status;
use common\models\user\UserUnusualLog;
use common\models\userFund\UserWithdrawOrder;
use yii\base\Exception;
use Yii;
/**
 * Class EmployeeInfo
 * @package api\modules\v1\models\employee
 */
class WithdrawOrder extends UserWithdrawOrder
{
    /**
     * 创建提现订单
     * @return array
     */
    public function createOrder() {
        $trans = \Yii::$app->db->beginTransaction();
        try {
            $user = (new User())->checkUser();
            // 检查用户信息
            (new \common\models\user\User()) -> checkInfo($user);

            # 零钱封禁
            UserUnusualLog::checkUserUnusual($user['id'],Status::USER_UNUSUAL_TYPE_MONEY);

            # 检查并发
            CacheKeys::checkFrequency($user['id']);

            $money = \Yii::$app->request->post('money',0);
            $bankId = \Yii::$app->request->post('bank_id',0);
            $type = \Yii::$app->request->post('type',0);  //1-余额钱包 2-橱窗钱包
            $withdrawWay = \Yii::$app->request->post('withdraw_way',Status::WITHDRAW_WAY_BANK);  //1-银行卡 2-支付宝
            $alipayAccount = \Yii::$app->request->post('alipay_account',"");  // 支付宝账号
            if ($money <= 0 ) {
                throw new Exception('提现金额有误');
            }

            if ($withdrawWay == Status::WITHDRAW_WAY_BANK) {
                if (!$bankId) {
                    throw new Exception('请选择银行卡');
                }

                $bankInfo = ReceiptBank::getOneByWhere(['id' => $bankId,'is_delete' => Status::COMMON_IS_NOT_DELETE]);
                if (empty($bankInfo)) {
                    throw new Exception("未知银行卡信息");
                }
            }

            if ($withdrawWay == Status::WITHDRAW_WAY_ALIPAY) {
                if (!$alipayAccount) {
                    throw new Exception('请填写支付宝账号');
                }

                if (!preg_match(Patterns::phoneNumber(), $alipayAccount) && !preg_match(Patterns::matchEmail(), $alipayAccount)) {
                    throw new Exception('支付宝账号格式不正确');
                }
            }

            if($type == Status::WITHDRAW_TYPE_SHOP){
                # 橱窗封禁
                UserUnusualLog::checkUserUnusual($user['id'],Status::USER_UNUSUAL_TYPE_GOODS);
                //卖方订单必须完成，算出来未完成的钱，要是体现的金额大于 完成的就不让提现
                $moneyWhere['sell_user'] = $user['id'];
                $moneyWhere['status'] = [
                    Status::USER_GOODS_ORDER_STATUS_WAITING_SEND,
                    Status::USER_GOODS_ORDER_STATUS_WAITING_RECEIVE,
                    Status::USER_GOODS_ORDER_SHENQING,
//                    Status::USER_GOODS_ORDER_RETURNOK,
                    Status::USER_GOODS_ORDER_RETURNNO,
                ];
                $noDoneMoney = GoodsOrder::getSumByWhere($moneyWhere,'real_money');
                $userMoney = $user['shop_money'] - $noDoneMoney;
                if($money > $userMoney){
                    throw new Exception('有暂无完成的订单，请完成订单后提现');
                }
            }

            if (!key_exists($type,Status::WITHDRAW_TYPE_MAP)) {
                throw new Exception('钱包类型不合法');
            }

            # 判定条件
            $config = static::getCommonByKey([
                'withdraw_min', "withdraw_max", "withdraw_everyday",
                'withdraw_start', "withdraw_end", "withdraw_fee","withdraw_fee_rate",'switch_withdraw'
            ]);

            $time = date("H:i");

            // switch_withdraw
            if($config['switch_withdraw'] != 1){
                throw new Exception("提现通道维护中,恢复第一时间通知");
            }

            # 检查交易时间
            if ($time < $config['withdraw_start'] || $time > $config['withdraw_end']) {
                throw new Exception("提现时间为每日{$config['withdraw_start']}~{$config['withdraw_end']}");
            }

            # 检查数量
            if ($money < $config['withdraw_min'] || $money > $config['withdraw_max']) {
                throw new Exception("提现金额在{$config['withdraw_min']} ~ {$config['withdraw_max']}CNY");
            }

            # 检查日限额
            if ($config['withdraw_everyday'] > 0) {
                # 获取今日提现金额
                $today['user_id'] = $user['id'];
                $todayAndWhere[] = ["between", "create_time", date("Y-m-d 00:00:00"), date("Y-m-d 23:59:59")];
                $todayTotal = (double) static::getSumByAndWhere($today, $todayAndWhere, "money");

                if ($todayTotal >= $config['withdraw_everyday']) {
                    throw new Exception('您今日提现数量已到上限');
                }

                $diff = $config['withdraw_everyday'] - $todayTotal;
                if ($diff < $money) {
                    throw new Exception("您今日还可以提{$diff}");
                }
            }


            $fee = $config['withdraw_fee'];
            $feeRate = $config['withdraw_fee_rate'] / 100;

            $feeMoney = bcmul($money,$feeRate,2) + $fee;
            $withdrawMoney = bcsub($money,$feeMoney,2);

            if ($withdrawMoney <= 0) {
                throw new Exception('打款金额有误');
            }

            $data['order_number'] = $this->_createOrderNumber();
            $data['bank_id'] = $bankId;
            $data['user_id'] = $user['id'];
            $data['money'] = $money;
            $data['real_withdraw_money'] = $withdrawMoney;
            $data['fee'] = $feeMoney;
            $data["rate"] = $feeRate;
            $data['create_time'] = date("Y-m-d H:i:s");
            $data['type'] = $type;
            $data['withdraw_way'] = $withdrawWay;
            $data['alipay_account'] = $alipayAccount;
            $res = static::insertData($data);
            if ($res === false) {
                throw new Exception('提现失败');
            }

            if ($type == Status::WITHDRAW_TYPE_MONEY) {
                // 余额信息
                UserMoneyLog::record(
                    $user['id'],
                    Status::PROP_TYPE_MONEY,
                    Status::MONEY_LOG_TYPE_WITHDRAW,
                    -1 * floatval($money),
                    Status::MONEY_LOG_TYPE_MAP[Status::MONEY_LOG_TYPE_WITHDRAW] ?? '',
                    '提现成功，单号：【' . $data['order_number'].'】',
                    $res
                );
            }

            if ($type == Status::WITHDRAW_TYPE_SHOP) {
                // 橱窗余额
                UserMoneyLog::record(
                    $user['id'],
                    Status::PROP_TYPE_SHOP_MONEY,
                    Status::SHOP_MONEY_LOG_TYPE_WITHDRAW,
                    -1 * floatval($money),
                    Status::SHOP_MONEY_LOG_TYPE_MAP[Status::SHOP_MONEY_LOG_TYPE_WITHDRAW] ?? '',
                    '提现成功，单号：【' . $data['order_number'].'】',
                    $res
                );
            }

            $moneyTypeName = Status::WITHDRAW_TYPE_MAP[$type] ?? '';

            // 发送IM信息
            $userMessage = [];
            $userMessage['message_type'] = (int) Status::MESSAGE_TYPE_USER_MONEY_MESSAGE;
            $userMessage['type'] = (int) Status::MESSAGE_TYPE_USER_MONEY_MESSAGE;
            $userMessage['title'] = $moneyTypeName."提现";
            $userMessage['money_title'] = "提现金额";
            $userMessage['money'] = (string) abs($money);
            $userMessage['desc'] = "提现".$money."元";
            $userMessage['mark'] = "你可以在钱包中查看相关记录";
            $userMessage['time'] = date('Y-m-d H:i:s');

            $config = static::getCommonByKey('money_user_id');
            (new Im()) -> sendUserMessage($user['tx_code'], $userMessage, $config);

            $trans->commit();
            return Functions::formatRestAPI(0, '提交成功，请等待审核');
        } catch (Exception $e) {
            $trans->rollBack();
            return Functions::formatRestAPI(1, $e->getMessage());
        }
    }


    /**
     * 获取历史提现记录
     * @param int $page
     * @param int $size
     *
     * @return array
     */
    public function getHistory($page = 1, $size = 20) {
        try {
            $user = (new User())->checkUser();
            $where = [
                "user_id" => $user['id']
            ];
            $order = "id DESC";

            $count = static::getCountByWhere($where);
            $data = static::setPageinationAPI($page, $size, $count);
            $offset = ($page - 1) * $size;
            $list = static::getObjectByWhere($where, ["id", "money", "real_withdraw_money", "fee", "create_time", "status", "failed_reason",'type'], $order, $offset, $size)
                ->asArray()->all();

            $result = [];

            foreach ($list as $k => $v) {
                $v['status_name'] = Status::WITHDRAW_STATUS_MAP[$v['status']];
                $v['type_name'] = Status::WITHDRAW_TYPE_MAP[$v['type']] ?? '';
                $result[] = $v;
            }

            $data['data'] = $result;

            return Functions::formatRestAPI(0, '', $data);
        } catch (Exception $e) {
            return Functions::formatRestAPI(1, $e->getMessage());
        }
    }



    public function getConfig() {
      try {
          $user = (new User())->checkUser();
          $config = static::getCommonByKey([
              'withdraw_min', "withdraw_max", "withdraw_everyday",
              'withdraw_start', "withdraw_end", "switch_withdraw", "withdraw_fee", "withdraw_fee_rate"
          ]);

          $ps = [
              "每天{$config['withdraw_start']}至{$config['withdraw_end']}开放提现",
              "每个用户每天可以提现{$config['withdraw_everyday']}元",
              "单次提现最小数量为{$config['withdraw_min']}元， 最大为{$config['withdraw_max']}元",
              "提现收费为费{$config['withdraw_fee_rate']}%， 每笔额外收取提现渠道费用为{$config['withdraw_fee']}元",
          ];
          $data['ps'] = Functions::FormatPs($ps);

          $data['min'] = $config['withdraw_min'];
          $data['max'] = $config['withdraw_max'];

          $data['fee'] = round($config['withdraw_fee_rate'], 2) / 100;
//          $data['fee'] = 0.03;
          $data['open'] = $config['switch_withdraw'] == 1;

          $moneyWhere['sell_user'] = $user['id'];
          $moneyWhere['status'] = [
              Status::USER_GOODS_ORDER_STATUS_WAITING_SEND,
              Status::USER_GOODS_ORDER_STATUS_WAITING_RECEIVE,
              Status::USER_GOODS_ORDER_SHENQING,
//              Status::USER_GOODS_ORDER_RETURNOK,
              Status::USER_GOODS_ORDER_RETURNNO,
          ];
          $noDoneMoney = GoodsOrder::getSumByWhere($moneyWhere,'money');
          //可提现余额
          $userMoney = $user['shop_money'] - $noDoneMoney;

          $data['shop_money'] = floatval($user['shop_money']);
          $data['withdraw_money'] =  floatval($userMoney)?:0;

          return Functions::formatRestAPI(0, '', $data);
      } catch (Exception $e) {
          return Functions::formatRestAPI(1, $e->getMessage());
      }
    }
}
